import { TransformNode } from '@babylonjs/core/Meshes/transformNode';
import { DefaultStage } from '../default-stage';
import * as Data from '../../data/data';
import { RawAssetsUrl } from '../../raw-assets-info';
import { CubeTexture } from '@babylonjs/core/Materials/Textures/cubeTexture';
import { Helper } from 'babylon-lib/tool/helper';
import { PBRMaterial } from '@babylonjs/core/Materials/PBR/pbrMaterial';


class ModelContainer {

    private static container: TransformNode;
    private static cubeTexture: CubeTexture;

    public static setTarget(model: TransformNode): void {
        model.parent = this.container;
        const tex = this.cubeTexture.clone();
        Helper.getChildMeshes(model).forEach(m => {
            if (m.material) {
                const mat = m.material as PBRMaterial;
                mat.reflectionTexture = tex;
            }
        });
    }

    public static reset(): void {
        this.container.getChildTransformNodes().forEach(n => {
            n.dispose(false, true);
        });
        this.container.position.set(0, 0, 0);
        this.container.scaling.set(1, 1, 1);
        this.container.rotation.set(0, 0, 0);
    }

    public static initialize(stage: DefaultStage): void {
        this.container = new TransformNode('model-container', stage.mainScene);
        const loader = stage.loader(stage.mainScene);
        this.cubeTexture = loader.getCubeTextureTaskInfo(RawAssetsUrl.lightCubePX)?.texture!;
        this.bindData();
    }

    private static bindData(): void {
        const model = this.container;
        Data.positionX.onChange((o, n) => {
            model.position.x = n;
        });
        Data.positionY.onChange((o, n) => {
            model.position.y = n;
        });
        Data.positionZ.onChange((o, n) => {
            model.position.z = n;
        });
        Data.rotationX.onChange((o, n) => {
            model.rotation.x = n;
        });
        Data.rotationY.onChange((o, n) => {
            model.rotation.y = n;
        });
        Data.rotationZ.onChange((o, n) => {
            model.rotation.z = n;
        });
        Data.scale.onChange((o, n) => {
            model.scaling.set(n, n, n);
        });
    }

}


export { ModelContainer };